#include "register_login.h"
#include "communicate.h"
#include "mysql_info.h"
// 生成随机字符（用于盐值）
char random_char() {
    const char* chars = "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
    return chars[rand() % 64];
}

// 生成$6$格式的盐值（SHA-512算法）
char* generate_salt_sha512(int rounds,char *salt,int salt_size) {
    char random_salt[17];  // 16字节随机盐 + 终止符

    // 生成16字节随机盐
    for (int i = 0; i < 16; i++) {
        random_salt[i] = random_char();
    }
    random_salt[16] = '\0';

    // 构建盐值字符串：$6$[rounds=N]$[salt]$
    if (rounds > 0) {
        snprintf(salt, salt_size, "$6$rounds=%d$%s$", rounds, random_salt);
    } else {
        snprintf(salt, salt_size, "$6$%s$", random_salt);  // 使用默认rounds
    }
    return salt;
}

// 加密密码（返回malloc分配的字符串，需手动free）
char* encrypt_password(const char* password, char *salt) {
    /* char* salt = generate_salt_sha512(rounds); */
    char* encrypted = crypt(password, salt);
    return strdup(encrypted);  // 复制结果，避免被后续调用覆盖
}

// 验证密码
int verify_password(const char* input, const char* stored_hash) {
    char* encrypted_input = crypt(input, stored_hash);
    /* printf("encrypted_input:%s\n",encrypted_input); */
    /* printf("stored_hash:%s\n",stored_hash); */
    return strcmp(encrypted_input, stored_hash) == 0;
}

int user_register(MYSQL*mysql,int netfd,char *user_name_pwd){
    char user_name[100]={0};
    char pwd[100]={0};
    char salt[100]={0};
    char ciphertext[300]={0};
    int flag=0;
    train_t train;    
    int register_flag=-1;
    char *token=strtok(user_name_pwd," ");
    if (token != NULL) {
        printf("第一个子字符串: %s\n", token);
        strcpy(user_name,token);
        // 以继续分割原字符串
        token = strtok(NULL," ");
        if (token != NULL) {
            printf("第二个子字符串: %s\n", token);
            strcpy(pwd,token);
            flag=1;
        }
    }
    if(flag){
        bzero(&train,sizeof(train));
        int ret=is_exist_username(mysql,user_name);
        if(!ret){                                                     
            bzero(salt,sizeof(salt));
            bzero(ciphertext,sizeof(ciphertext));
            generate_salt_sha512(0,salt,sizeof(salt));
            printf("salt:%s\n",salt);
            char * hash=encrypt_password(pwd,salt);
            strcpy(ciphertext,hash);
            ciphertext[strlen(ciphertext)]='\0';
            printf("通过salt算出来的密文:%s\n",ciphertext);
            user_info_t new_user;
            strcpy(new_user.user_name, user_name);
            strcpy(new_user.salt, salt);
            strcpy(new_user.encrypted_password, ciphertext);
            free(hash);
            if(add_one_user(mysql,&new_user)){
                log_info(mysql,new_user.id,"register",1,"register sucess");
                train.type=REGISTER_SUCESS;
                train.length=strlen("注册成功!");
                strcpy(train.data,"注册成功!");
                register_flag=0;
            }
        }else {
            log_info(mysql,-1,"register",0,"user already exist!");
            train.type=REGISTER_FAILD;
            train.length=strlen("用户已存在!");
            strcpy(train.data,"用户已存在!");
        }
    }else{
        train.type=REGISTER_FAILD;
        train.length=strlen("格式错误!");
        strcpy(train.data,"格式错误!");
    }
    send(netfd,&train,sizeof(train.type)+sizeof(train.length)+train.length,0);
    return register_flag;
}

int user_login(MYSQL*mysql,int netfd,char *user_name_pwd){
    char user_name[100]={0};
    char pwd[100]={0};
    int flag=0;
    train_t train;
    char login_msg[300]={0};
    char last_login_time[100]={0};
    int login_flag=-1;
    char *token=strtok(user_name_pwd," ");
    if (token != NULL) {
        printf("第一个子字符串: %s\n", token);
        strcpy(user_name,token);
        // 以继续分割原字符串
        token = strtok(NULL," ");
        if (token != NULL) {
            printf("第二个子字符串: %s\n", token);
            strcpy(pwd,token);
            flag=1;
        }
    }
    if(flag){
        bzero(&train,sizeof(train));
        int ret=is_exist_username(mysql,user_name);
        if(ret){
            user_info_t user;
            int user_id=get_user_id_by_user_name(mysql,user_name);
            get_user_by_id(mysql,&user,user_id);
            /* printf("user_pwd%s\n",user_pwd); */
            /* printf("result:%d\n",verify_password(user_pwd,user.encrypted_password)); */
            if(verify_password(pwd,user.encrypted_password)){
                train.type=LOGIN_SUCESS;
                bzero(last_login_time,sizeof(last_login_time));
                bzero(login_msg,sizeof(login_msg));
                int ret=get_last_login_time(mysql,last_login_time,user_id);
                strcat(login_msg,"登录成功!");
                if(ret){
                    strcat(login_msg," ");
                    strcat(login_msg,"上一次登录时间:");
                    strcat(login_msg,last_login_time);
                }
                train.length=strlen(login_msg);
                strcpy(train.data,login_msg);
                log_info(mysql,user_id,"login",1,"login sucess");
                login_flag=0;
            }else {
                train.type=LOGIN_FAILD;
                train.length=strlen("密码错误!");
                strcpy(train.data,"密码错误!");
                log_info(mysql,user_id,"login",0,"password wrong");
            }
        }else {
            train.type=LOGIN_FAILD;
            train.length=strlen("没有该用户!");
            strcpy(train.data,"没有该用户!");
            log_info(mysql,-1,"login",0,"no such user!");
        }
    }else{
        train.type=LOGIN_FAILD;
        train.length=strlen("格式错误!");
        strcpy(train.data,"格式错误!");
    }
    send(netfd,&train,sizeof(train.type)+sizeof(train.length)+train.length,0);
    return login_flag;
}
